/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package merlion.scm.lcm.entity;

import java.io.Serializable;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.List;
import java.util.Random;
import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
import merlion.crm.sopm.entity.ItemLine;
import merlion.crm.sopm.entity.SalesOrder;
import merlion.frm.bpm.entity.Invoice;
import merlion.crm.slcm.entity.Address;
import merlion.crm.sopm.entity.PurchaseOrder;
import merlion.crm.sopm.entity.SalesQuotation;

/**
 *
 * @author Yuwei
 */
@Entity
public class DeliveryOrder implements Serializable {
    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;
    private String deliveryOrderIdStr;
    private Boolean active;
    private String status;
    private String indicativeLeadTime;
    private Timestamp indicativeLeadTimeTS;
    private String leadTime;
    private Timestamp leadTimeTS;
    private Boolean urgent;
    private Double subtotal;
    private Double specialDiscount;
    private Double memberDiscount;
    private Double orderDiscount;
    private Double tax;
    private Double total;
    private Timestamp timeCreated;
    private int priority;
    @ManyToOne(targetEntity=SalesOrder.class, cascade={CascadeType.PERSIST, CascadeType.MERGE}, fetch=FetchType.EAGER)
    private SalesOrder salesOrder;
    @ManyToOne(targetEntity=PurchaseOrder.class, cascade={CascadeType.PERSIST, CascadeType.MERGE}, fetch=FetchType.EAGER)
    private PurchaseOrder purchaseOrder;
    @ManyToOne(targetEntity=SalesQuotation.class, cascade={CascadeType.PERSIST, CascadeType.MERGE}, fetch=FetchType.EAGER)
    private SalesQuotation salesQuotation;
    @ManyToOne (targetEntity=Address.class, cascade={CascadeType.PERSIST,CascadeType.MERGE}, fetch=FetchType.EAGER)
    private Address shippingAddress;
    @OneToMany (targetEntity=ItemLine.class, cascade={CascadeType.PERSIST,CascadeType.MERGE}, fetch=FetchType.EAGER)
    private Collection<ItemLine> itemLines;
    @OneToOne(targetEntity = Invoice.class, cascade = {CascadeType.PERSIST, CascadeType.MERGE}, fetch = FetchType.EAGER)
    private Invoice invoice;
    @OneToOne(targetEntity = PackingOrder.class, cascade = {CascadeType.PERSIST, CascadeType.MERGE}, fetch = FetchType.EAGER)
    private PackingOrder packingOrder;
    @OneToOne(targetEntity = PickingOrder.class, cascade = {CascadeType.PERSIST, CascadeType.MERGE}, fetch = FetchType.EAGER)
    private PickingOrder pickingOrder;
    @OneToOne(targetEntity = ShippingOrder.class, cascade = {CascadeType.PERSIST, CascadeType.MERGE}, fetch = FetchType.EAGER)
    private ShippingOrder shippingOrder;


    public DeliveryOrder(){
        leadTime = "";
        leadTimeTS = new Timestamp(new Date().getTime());
        indicativeLeadTime = "";
        indicativeLeadTimeTS = new Timestamp(new Date().getTime());
        urgent = Boolean.FALSE;
        subtotal = (double)0;
        orderDiscount = (double)0;
        memberDiscount = (double)0;
        specialDiscount = (double)0;
        salesOrder = new SalesOrder();
        purchaseOrder = new PurchaseOrder();
        shippingAddress = new Address();
        itemLines = new ArrayList<ItemLine>();
        invoice = null;
        active = false;
        Random rand = new Random();
        long seed = new Date().getTime() + (long)rand.nextInt(10000);
        priority = -1;
        timeCreated = new Timestamp(seed);
        packingOrder = null;
        pickingOrder = null;
        shippingOrder = null;
        deliveryOrderIdStr = "";
    }
    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getIndicativeLeadTime() {
        return indicativeLeadTime;
    }

    public void setIndicativeLeadTime(String indicativeLeadTime) {
        this.indicativeLeadTime = indicativeLeadTime;
    }

    public Timestamp getIndicativeLeadTimeTS() {
        return indicativeLeadTimeTS;
    }

    public void setIndicativeLeadTimeTS(Timestamp indicativeLeadTimeTS) {
        this.indicativeLeadTimeTS = indicativeLeadTimeTS;
    }
    
    public int getPriority() {
        return priority;
    }

    public void setPriority(int priority) {
        this.priority = priority;
    }

    public String getStatus() {
        return status;
    }

    public void setStatus(String status) {
        this.status = status;
    }
    
    public Invoice getInvoice() {
        return invoice;
    }

    public void setInvoice(Invoice invoice) {
        this.invoice = invoice;
    }

    public Collection<ItemLine> getItemLines() {
        return itemLines;
    }

    public void setItemLines(Collection<ItemLine> itemLines) {
        this.itemLines = itemLines;
    }

    public String getLeadTime() {
        return leadTime;
    }

    public void setLeadTime(String leadTime) {
        this.leadTime = leadTime;
    }

    public Timestamp getLeadTimeTS() {
        return leadTimeTS;
    }

    public void setLeadTimeTS(Timestamp leadTimeTS) {
        this.leadTimeTS = leadTimeTS;
    }

    public SalesOrder getSalesOrder() {
        return salesOrder;
    }

    public void setSalesOrder(SalesOrder salesOrder) {
        this.salesOrder = salesOrder;
    }

    public Address getShippingAddress() {
        return shippingAddress;
    }

    public void setShippingAddress(Address shippingAddress) {
        this.shippingAddress = shippingAddress;
    }

    public Double getSubtotal() {
        return subtotal;
    }

    public void setSubtotal(Double subtotal) {
        this.subtotal = subtotal;
    }

    public Double getTax() {
        return tax;
    }

    public void setTax(Double tax) {
        this.tax = tax;
    }

    public Double getTotal() {
        return total;
    }

    public void setTotal(Double total) {
        this.total = total;
    }

    public Boolean getUrgent() {
        return urgent;
    }

    public void setUrgent(Boolean urgent) {
        this.urgent = urgent;
    }

    public Boolean getActive() {
        return active;
    }

    public void setActive(Boolean active) {
        this.active = active;
    }

    public PurchaseOrder getPurchaseOrder() {
        return purchaseOrder;
    }

    public void setPurchaseOrder(PurchaseOrder purchaseOrder) {
        this.purchaseOrder = purchaseOrder;
    }

    public SalesQuotation getSalesQuotation() {
        return salesQuotation;
    }

    public void setSalesQuotation(SalesQuotation salesQuotation) {
        this.salesQuotation = salesQuotation;
    }

    public Timestamp getTimeCreated() {
        return timeCreated;
    }

    public void setTimeCreated(Timestamp timeCreated) {
        this.timeCreated = timeCreated;
    }

    public Double getMemberDiscount() {
        return memberDiscount;
    }

    public void setMemberDiscount(Double memberDiscount) {
        this.memberDiscount = memberDiscount;
    }

    public Double getOrderDiscount() {
        return orderDiscount;
    }

    public void setOrderDiscount(Double orderDiscount) {
        this.orderDiscount = orderDiscount;
    }

    public Double getSpecialDiscount() {
        return specialDiscount;
    }

    public void setSpecialDiscount(Double specialDiscount) {
        this.specialDiscount = specialDiscount;
    }

    public PackingOrder getPackingOrder() {
        return packingOrder;
    }

    public void setPackingOrder(PackingOrder packingOrder) {
        this.packingOrder = packingOrder;
    }

    public PickingOrder getPickingOrder() {
        return pickingOrder;
    }

    public void setPickingOrder(PickingOrder pickingOrder) {
        this.pickingOrder = pickingOrder;
    }

    public ShippingOrder getShippingOrder() {
        return shippingOrder;
    }

    public void setShippingOrder(ShippingOrder shippingOrder) {
        this.shippingOrder = shippingOrder;
    }

    public String getDeliveryOrderIdStr() {
        return deliveryOrderIdStr;
    }

    public void setDeliveryOrderIdStr(String deliveryOrderIdStr) {
        this.deliveryOrderIdStr = deliveryOrderIdStr;
    }

    
    @Override
    public DeliveryOrder clone(){
        DeliveryOrder d = new DeliveryOrder();
        d.setActive(this.getActive());
        d.setInvoice(null);
        d.setItemLines(new ArrayList<ItemLine>());
        for(ItemLine i: this.itemLines){
            i = i.clone();
            d.getItemLines().add(i);
        }
        d.setLeadTime(this.getLeadTime());
        d.setLeadTimeTS(this.leadTimeTS);
        d.setMemberDiscount(memberDiscount);
        d.setOrderDiscount(orderDiscount);
        d.setPackingOrder(null);
        d.setPickingOrder(null);
        d.setPriority(0);
        d.setPurchaseOrder(null);
        d.setSalesOrder(null);
        d.setSalesQuotation(null);
        d.setShippingAddress(shippingAddress);
        d.setShippingOrder(null);
        d.setSpecialDiscount(specialDiscount);
        d.setStatus(status);
        d.setSubtotal(subtotal);
        d.setTax(tax);
        d.setTimeCreated(new Timestamp (System.currentTimeMillis()));
        d.setTotal(total);
        d.setUrgent(urgent);
        
        return d;
    }
    
    @Override
    public int hashCode() {
        int hash = 0;
        hash += (id != null ? id.hashCode() : 0);
        return hash;
    }

    @Override
    public boolean equals(Object object) {
        if (!(object instanceof DeliveryOrder)) {
            return false;
        }
        DeliveryOrder other = (DeliveryOrder) object;
        // Compare timestamp
        if(!this.timeCreated.equals(other.timeCreated))
            return false;
        
        return true;
    }

    @Override
    public String toString() {
        return "merlion.scm.lcm.entity.DeliveryOrder[ id=" + id + " ]";
    }


    
}
